class Foo {
    condition_variable m_cv;
    mutex m_mtx;
    int m_nFlg;
public:
    Foo() {
        
        m_nFlg=1;
    }

    void first(function<void()> printFirst) {
        
        // printFirst() outputs "first". Do not change or remove this line.
        unique_lock<mutex> lock(m_mtx);
        m_cv.wait(lock,[=](){

            return m_nFlg==1;
        });
        printFirst();
        m_nFlg=2;
        m_cv.notify_all();
    }

    void second(function<void()> printSecond) {
        
        // printSecond() outputs "second". Do not change or remove this line.
        unique_lock<mutex> lock(m_mtx);
        m_cv.wait(lock,[=](){

            return m_nFlg==2;
        });
        printSecond();
        m_nFlg=3;
        m_cv.notify_all();
    }

    void third(function<void()> printThird) {
        
        // printThird() outputs "third". Do not change or remove this line.
        unique_lock<mutex> lock(m_mtx);
        m_cv.wait(lock,[=](){

            return m_nFlg==3;
        });
        printThird();
        m_nFlg=1;
        m_cv.notify_all();
    }
};
